package com.example.transaction.sys.controller;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.example.transaction.common.vo.Result;
import com.example.transaction.sys.entity.Announcement;
import com.example.transaction.sys.entity.Item;
import com.example.transaction.sys.entity.LoginLog;
import com.example.transaction.sys.entity.User;
import com.example.transaction.sys.service.IClassfyService;
import com.example.transaction.sys.service.IItemClassfyService;
import com.example.transaction.sys.service.IItemService;
import com.example.transaction.sys.service.IUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.CacheEvict;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.stereotype.Controller;

import java.util.*;

/**
 * <p>
 *  前端控制器
 * </p>
 *
 * @author zh
 * @since 2023-06-20
 */
@RestController
@RequestMapping("/sys/item")
public class ItemController {
    @Autowired
    private IItemService itemService;

    @Autowired
    private IUserService userService;

    @Autowired
    private IItemClassfyService itemClassfyService;

    @Autowired
    private IClassfyService classfyService;

    @Cacheable(value = "items", key = "'allItems'")
    @GetMapping("/all")
    public Result<List<Item>> getAllItem(){
        List<Item>list=itemService.list();
        return Result.success(list,"查询成功");
    }

    /**
     * 根据物品id查找信息
     * @param id
     * @return
     */
    @Cacheable(value = "items", key = "#id")
    @GetMapping("/{id}")
    public Result<Item>getItemById(@PathVariable("id")Integer id){
        Item item=itemService.getById(id);
        System.out.println(item);
        return Result.success(item);
    }

    /**
     * 新增商品接口
     * @param item
     * @return
     */
    @CacheEvict(value = "items", allEntries = true)
    @PostMapping("/addItem")
    public Result<?>addItem(@RequestBody Item item){
        try {
            itemService.save(item);
        }catch (Exception e){
            return Result.fail("新增失败");
        }
        return Result.success("新增商品成功");
    }

    /**
     * 查询所有商品(随机)，或者按条件查询(名称模糊搜索，价格区间限定)
     * @param
     * @param
     * @param pageNo
     * @param pageSize
     * @return
     */
    @Cacheable(value = "items", key = "'allItems'+#itemName+#maxprice+#classfyName+#minprice+#itemStatus+#userName+#itemImage+#pageNo+#pageSize")
    @GetMapping("/list")
    public Result<Map<String,Object>>getItemList(@RequestParam(value = "itemName",required = false)String itemName,
                                                 @RequestParam(value = "maxprice",required = false)String maxprice,
                                                 @RequestParam(value = "classfyName",required = false)String classfyName,
                                                 @RequestParam(value = "minprice",required = false)String minprice,
                                                 @RequestParam(value = "itemStatus",required = false)String itemStatus,
                                                 @RequestParam(value = "userName",required = false)String userName,
                                                 @RequestParam(value = "itemImage",required = false)String itemImage,
                                                 @RequestParam(value = "pageNo")Long pageNo,
                                                 @RequestParam(value = "pageSize")Long pageSize){
        LambdaQueryWrapper<Item> wrapper=new LambdaQueryWrapper<>();
        if(itemName!=null&&itemName!="") {
            wrapper.and(qw -> qw
                    .like(StringUtils.hasLength(itemName), Item::getItemName, itemName)
                    .or()
                    .like(StringUtils.hasLength(itemName), Item::getItemDescription, itemName)
            );
        }
        try {
            wrapper.lt(StringUtils.hasLength(maxprice), Item::getPrice, Double.parseDouble(maxprice));
        }catch (Exception e){
            e.printStackTrace();
        }
        try {
            wrapper.gt(StringUtils.hasLength(minprice), Item::getPrice, Double.parseDouble(minprice));
        }catch (Exception e){
            e.printStackTrace();
        }
        wrapper.eq(StringUtils.hasLength(itemStatus),Item::getItemStatus,itemStatus);
        wrapper.eq(StringUtils.hasLength(itemImage),Item::getItemImage,itemImage);

        if (StringUtils.hasLength(userName)) {
            List<Integer> userIds = userService.getUserIdsByUsername(userName);
            if (!userIds.isEmpty()) {
                wrapper.in(Item::getUserID, userIds);
            }
            else{
                List<Map<String, Object>> rows = new ArrayList<>();
                Map<String, Object> data = new HashMap<>();
                data.put("total", 0);
                data.put("rows", rows);
                return Result.success(data);
            }
        }

        if (StringUtils.hasLength(classfyName)) {
            Integer classfyID=classfyService.getclassfyIDByClassfyName(classfyName);
            List<Integer> itemIds = itemClassfyService.getItemIdsByClassfyID(classfyID);
            if (!itemIds.isEmpty()) {
                wrapper.in(Item::getItemID, itemIds);
            }
            else{
                List<Map<String, Object>> rows = new ArrayList<>();
                Map<String, Object> data = new HashMap<>();
                data.put("total", 0);
                data.put("rows", rows);
                return Result.success(data);
            }
        }

        // 按随机顺序排序
        wrapper.last("ORDER BY RAND()");

        Page<Item> page=new Page<>(pageNo,pageSize);
        itemService.page(page,wrapper);
        Map<String,Object>data=new HashMap<>();
        data.put("total",page.getTotal());
        data.put("rows",page.getRecords());
        return Result.success(data);
    }

    /**
     * 查询所有商品(不随机)，或者按条件查询(名称模糊搜索，价格区间限定)
     * @param
     * @param
     * @param pageNo
     * @param pageSize
     * @return
     */
    @Cacheable(value = "items", key = "'noRandAllItems'+#itemName+#maxprice+#classfyName+#minprice+#itemStatus+#userName+#pageNo+#pageSize")
    @GetMapping("/listNoRand")
    public Result<Map<String,Object>>getItemListNoRand(@RequestParam(value = "itemName",required = false)String itemName,
                                                 @RequestParam(value = "maxprice",required = false)String maxprice,
                                                 @RequestParam(value = "classfyName",required = false)String classfyName,
                                                 @RequestParam(value = "minprice",required = false)String minprice,
                                                 @RequestParam(value = "itemStatus",required = false)String itemStatus,
                                                 @RequestParam(value = "userName",required = false)String userName,
                                                 @RequestParam(value = "pageNo")Long pageNo,
                                                 @RequestParam(value = "pageSize")Long pageSize){
        LambdaQueryWrapper<Item> wrapper=new LambdaQueryWrapper<>();
        if(itemName!=null&&itemName!="") {
            wrapper.and(qw -> qw
                    .like(StringUtils.hasLength(itemName), Item::getItemName, itemName)
                    .or()
                    .like(StringUtils.hasLength(itemName), Item::getItemDescription, itemName)
            );
        }
        try {
            wrapper.lt(StringUtils.hasLength(maxprice), Item::getPrice, Double.parseDouble(maxprice));
        }catch (Exception e){
            e.printStackTrace();
        }
        try {
            wrapper.gt(StringUtils.hasLength(minprice), Item::getPrice, Double.parseDouble(minprice));
        }catch (Exception e){
            e.printStackTrace();
        }
        wrapper.eq(StringUtils.hasLength(itemStatus),Item::getItemStatus,itemStatus);

        if (StringUtils.hasLength(userName)) {
            List<Integer> userIds = userService.getUserIdsByUsername(userName);
            if (!userIds.isEmpty()) {
                wrapper.in(Item::getUserID, userIds);
            }
            else{
                List<Map<String, Object>> rows = new ArrayList<>();
                Map<String, Object> data = new HashMap<>();
                data.put("total", 0);
                data.put("rows", rows);
                return Result.success(data);
            }
        }

        if (StringUtils.hasLength(classfyName)) {
            Integer classfyID=classfyService.getclassfyIDByClassfyName(classfyName);
            List<Integer> itemIds = itemClassfyService.getItemIdsByClassfyID(classfyID);
            if (!itemIds.isEmpty()) {
                wrapper.in(Item::getItemID, itemIds);
            }
            else{
                List<Map<String, Object>> rows = new ArrayList<>();
                Map<String, Object> data = new HashMap<>();
                data.put("total", 0);
                data.put("rows", rows);
                return Result.success(data);
            }
        }

        // 添加倒序排序条件，根据主键（itemID）倒序排列
        wrapper.orderByDesc(Item::getItemID);

        Page<Item> page=new Page<>(pageNo,pageSize);
        itemService.page(page,wrapper);
        Map<String,Object>data=new HashMap<>();
        data.put("total",page.getTotal());
        data.put("rows",page.getRecords());
        return Result.success(data);
    }

    /**
     * 删除商品
     * @param id
     * @return
     */
    @CacheEvict(value = "items", allEntries = true)
    @DeleteMapping("/{id}")
    public Result<Item>deleteItemById(@PathVariable("id")Integer id){
        itemService.removeById(id);
        return Result.success("删除商品成功");
    }

    /**
     * 更新商品状态
     * @param id
     * @param status
     * @return
     */
    @CacheEvict(value = "items", allEntries = true)
    @PutMapping("/status/{id}")
    public Result<Item> updateItemStatus(@PathVariable("id") Integer id,
                                         @RequestParam("status") String status) {
        LambdaQueryWrapper<Item> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Item::getItemID, id);
        Item item=itemService.getOne(wrapper);
        item.setItemStatus(status);
        itemService.updateById(item);
        return Result.success("更新商品状态成功");
    }

    /**
     * 更新商品 信息
     * @return
     */
    @CacheEvict(value = "items", allEntries = true)
    @PutMapping("/update/{id}")
    public Result<Item> updateItem(@PathVariable("id") Integer id,
                                   @RequestParam(value = "itemName") String itemName,
                                   @RequestParam(value = "itemDescription") String itemDescription,
                                   @RequestParam(value = "price") Double price,
                                   @RequestParam(value = "itemImage") String itemImage) {
        Item item = new Item();
        item.setItemID(id);
        item.setItemName(itemName);
        item.setItemDescription(itemDescription);
        item.setPrice(price);
        item.setItemImage(itemImage);
        itemService.updateById(item);
        return Result.success("更新商品信息成功");
    }

    /**
     * 通过userID查找Item的信息
     * @param userID
     * @return
     */
    @Cacheable(value = "items", key = "user+#userID")
    @GetMapping("/items/{userID}")
    public Result<List<Item>> getItemByUserID(@PathVariable("userID") Integer userID){
        LambdaQueryWrapper<Item> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Item::getUserID, userID);
        List<Item> itemList = itemService.list(wrapper);
        return Result.success(itemList);
    }

    /**
     * 根据itemID更改item的信息
     * @param item
     * @return
     */
    @CacheEvict(value = "items", key = "#item.itemID",allEntries = true)
    @PutMapping("/updateByItemID")
    public Result<?>updateItem(@RequestBody Item item){
        try {
            itemService.updateById(item);
        }catch (Exception e){
            return Result.fail("修改失败");
        }
        return Result.success("修改商品成功");
    }
}
